import store from '@/store'
import router from '@/router'
import { localStorageSet, localStorageGet, sessionStorageClear, cookieSet, cookieGet, cookieClear } from '@/utils/storage-util'
import { formatDate } from '@/utils/time-util'
import { refreshTokenApi } from '@/api/oauth'

/** 清除用户登录信息 **/
export function clearLoginInfo () {
  sessionStorageClear()
  cookieClear()
  store.commit('resetStore')
  router.options.isAddDynamicMenuRoutes = false
}

/** 是否有权限 **/
export function isAuth (key) {
  if (key === undefined) {
    return true
  }
  return store.getters.permissions.indexOf(key) !== -1 || false
}

/** 是否需要登录 true需要登录 **/
export function isLogin () {
  let accessToken = cookieGet('accessToken')
  if (!accessToken) {
    // 已过期，无法刷新
    return true
  }
  // 查看是否可以刷新token
  let expiredTime = cookieGet('expiredTime')
  if (expiredTime) {
    let nowTime = new Date().getTime()
    if ((expiredTime - nowTime) / 1000 > 6 * 60) {
      // 未到过期时间
      return false
    }
  } else {
    // 已过期，无法刷新
    return true
  }
  let isRefreshToken = localStorageGet('IS_REFRESH_TOKEN')
  if (isRefreshToken || isRefreshToken === 'true') {
    return false
  }
  let refreshToken = cookieGet('refreshToken')
  if (!refreshToken) {
    return true
  }
  localStorageSet('IS_REFRESH_TOKEN', true)
  refreshTokenApi(refreshToken).then(res => {
    localStorageSet('IS_REFRESH_TOKEN', false)
    if (res && res.code === 10000) {
      let data = res.data
      let expiredTime = formatDate(new Date().getTime() + (data.expiration * 1000), 'yyyy-MM-dd HH:mm:ss')
      cookieSet('accessToken', data.accessToken, expiredTime)
      cookieSet('expiredTime', expiredTime.getTime())
      return false
    } else {
      return true
    }
  }).catch(() => {
    return true
  })
  return true
}

/** 折线图方法 **/
export function debounce (func, wait, immediate) {
  let timeout, args, context, timestamp, result

  const later = function () {
    // 据上一次触发时间间隔
    const last = +new Date() - timestamp

    // 上次被包装函数被调用时间间隔last小于设定时间间隔wait
    if (last < wait && last > 0) {
      timeout = setTimeout(later, wait - last)
    } else {
      timeout = null
      // 如果设定为immediate===true，因为开始边界已经调用过了此处无需调用
      if (!immediate) {
        result = func.apply(context, args)
        if (!timeout) context = args = null
      }
    }
  }

  return function (...args) {
    context = this
    timestamp = +new Date()
    const callNow = immediate && !timeout
    // 如果延时不存在，重新设定延时
    if (!timeout) timeout = setTimeout(later, wait)
    if (callNow) {
      result = func.apply(context, args)
      context = args = null
    }

    return result
  }
}

/** 将列表字段提取转换成指定列表格式 **/
export function mapTranslate (data, id = 'id', name = 'name') {
  if (data === undefined || data.length === 0) {
    return []
  }
  let res = []
  data.forEach(item => {
    res.push({ value: item[id], key: item[name] })
  })
  return res
}

/** 树形数据转换 **/
export function treeDataTranslate (data, id = 'id', pid = 'parentId') {
  let res = []
  let temp = {}
  for (let i = 0; i < data.length; i++) {
    temp[data[i][id]] = data[i]
  }
  for (let k = 0; k < data.length; k++) {
    if (temp[data[k][pid]] && data[k][id] !== data[k][pid]) {
      if (!temp[data[k][pid]]['children']) {
        temp[data[k][pid]]['children'] = []
      }
      if (!temp[data[k][pid]]['_level']) {
        temp[data[k][pid]]['_level'] = 1
      }
      data[k]['_level'] = temp[data[k][pid]]._level + 1
      temp[data[k][pid]]['children'].push(data[k])
    } else {
      res.push(data[k])
    }
  }
  return res
}

/** 树格式化 **/
export function treeFormat (data, value = 'id', label = 'name', children = 'subs', isChildren = false, isKeep = false, keepField = '', keepFieldReplace = '') {
  if (data === undefined || data === null || data.length === 0) {
    return isChildren ? [] : null
  }
  let res = []
  data.forEach(item => {
    let _item = {
      value: item[value],
      label: item[label],
      children: treeFormat(item[children], value, label, children, isChildren, isKeep, keepField, keepFieldReplace)
    }
    if (isKeep && keepField && keepField.length > 0) {
      if (keepFieldReplace && keepFieldReplace.length > 0) {
        _item[keepFieldReplace] = item[keepField]
      } else {
        _item[keepField] = item[keepField]
      }
    }
    res.push(_item)
  })
  return res
}

/** 树结果检索 **/
export function treeRetrieval (data, retrievalField = 'id', retrievalValue = '', children = 'subs') {
  if (data === undefined || data === null || data.length === 0) {
    return null
  }
  for (let i = 0; i < data.length; i++) {
    let item = data[i]
    if (item[retrievalField] === retrievalValue) {
      return item
    }
    let res = treeRetrieval(item[children], retrievalField, retrievalValue, children)
    if (res !== undefined && res !== null) {
      return res
    }
  }
  return null
}

/** 遍历树 **/
export function treeForEach(data, children, func) {
  if (data === undefined || data === null || data.length === 0 || func === undefined) {
    return
  }
  for (let i = 0; i < data.length; i++) {
    let item = data[i]
    if (func && func instanceof Function) {
      func(item)
    }
    treeForEach(item[children], children, func)
  }
}

/** 层级选中，根据选中id获取选中值 **/
export function cascaderSuperior(data = [], sub = false, subFieldName = '', targetValue) {
  return cascaderSuperiorBase(data, data, sub, subFieldName, targetValue)
}
function cascaderSuperiorBase(data = [], subData = [], sub = false, subFieldName = '', targetValue, values = []) {
  if (subFieldName === undefined || subFieldName === null || subFieldName.length === 0) {
    return []
  }
  if (subData === undefined || subData === null || subData.length === 0) {
    return
  }
  if (values === undefined || values === null || values.length === 0) {
    values = [ targetValue ]
  }
  let eachData = []
  Object.assign(eachData, data)
  if (sub) {
    eachData = subData
  }
  for (let i = 0; i < eachData.length; i++) {
    let item = eachData[i]
    if (item.id === targetValue) {
      if (item.parentId === '0') {
        return values
      }

      values.unshift(item.parentId)
      cascaderSuperiorBase(data, data, false, subFieldName, item.parentId, values)
    } else {
      cascaderSuperiorBase(data, item[subFieldName], true, subFieldName, targetValue, values)
    }
  }
  return values
}
